package com.afdor.rws.dtm.transaction;

import java.util.Arrays;
import java.util.Objects;

/**
 * 二阶段分布式事务中本地事务的事务传播性
 *
 * @author 悭梵
 * @date Created in 2018-10-12 11:27
 * @see org.springframework.transaction.TransactionDefinition
 * @see org.springframework.transaction.annotation.Propagation
 */
public enum Propagation {

    /**
     * @see org.springframework.transaction.TransactionDefinition.PROPAGATION_REQUIRED
     * @see org.springframework.transaction.annotation.Propagation.REQUIRED
     */
    REQUIRED(0),

    /**
     * @see org.springframework.transaction.TransactionDefinition.PROPAGATION_SUPPORTS
     * @see org.springframework.transaction.annotation.Propagation.SUPPORTS
     */
    SUPPORTS(1),

    /**
     * @see org.springframework.transaction.TransactionDefinition.PROPAGATION_MANDATORY
     * @see org.springframework.transaction.annotation.Propagation.MANDATORY
     */
    MANDATORY(2),

    /**
     * @see org.springframework.transaction.TransactionDefinition.PROPAGATION_REQUIRES_NEW
     * @see org.springframework.transaction.annotation.Propagation.REQUIRES_NEW
     */
    REQUIRES_NEW(3),

    /**
     * @see org.springframework.transaction.TransactionDefinition.PROPAGATION_NOT_SUPPORTED
     * @see org.springframework.transaction.annotation.Propagation.NOT_SUPPORTED
     */
    NOT_SUPPORTED(4),

    /**
     * @see org.springframework.transaction.TransactionDefinition.PROPAGATION_NEVER
     * @see org.springframework.transaction.annotation.Propagation.NEVER
     */
    NEVER(5),

    /**
     * @see org.springframework.transaction.TransactionDefinition.PROPAGATION_NESTED
     * @see org.springframework.transaction.annotation.Propagation.NESTED
     */
    NESTED(6);


    private final int value;

    Propagation(final int value) {
        this.value = value;
    }

    /**
     * Gets value.
     *
     * @return the value
     */
    public int value() {
        return this.value;
    }

    public static Propagation acquireByValue(final int value) {
        return Arrays.stream(Propagation.values())
                .filter(v -> Objects.equals(v.value(), value))
                .findFirst()
                .orElse(Propagation.REQUIRES_NEW);
    }

}